Плохо! Плохо!:  0
Показано с 1 по 1 из 1

Тема: [MZ] Плагины сделанные с помощью ИИ

  1. #1

    По умолчанию [MZ] Плагины сделанные с помощью ИИ

    Пока пытался разработать свою игру, используя ИИ для практически всего, от рисунков и до кода, у меня в конце концов пригорело от своей несостоятельности в плане графики, так как ИИ пока что в плане рисования ндля отдельных элементов, совсем не пригоден (особенно если учитывать, что я пользовался бесплатными версиями ИИ). Но плагины вышли в полне рабочие и хоть я решил бросить разработку, составленные плагины сжигать как то жалко, по этому отдаю на общее рассмотрение и использование.

    Плагины делались под боёвку с данного сайта https://www.srpgmaker.com/p/plugins.html

    1 - Не настроенный плагин позволяющий добавлять дополнительные паралаксы, не смог настроить, что бы они были под игроком, но если вам требуется, то можно использовать легко для, к примеру, облаков (настройка минимальная, лишь нужно ввести в примечание карты нужные данные)


    Спойлер Скировать-Вставит:
    /*:
    * @target MZ
    * @plugindesc Advanced parallax system with layer control, animations, and event-based triggers. Version 1.0
    * @author YourName
    * @help
    * ================================================== ==========================
    * ПЛАГИН ДЛЯ РАСШИРЕННЫХ ПАРАЛЛАКС-СЛОЕВ
    * ================================================== ==========================
    *
    * ◊ Основные возможности:
    * - Добавление неограниченного количества параллакс-слоёв на карту
    * - Гибкое управление глубиной (под событиями, над событиями, над игроком)
    * - Анимация слоёв (прокрутка, мерцание, смена оттенка, прозрачность)
    * - Управление через команды плагина или заметки карты
    *
    * ◊ Команды плагина:
    * addParallaxLayer [файл] [xСкорость] [yСкорость] [z] [прозрачность] [оттенок]
    * removeParallaxLayer [индекс]
    * animateParallax [индекс] [свойство] [значение] [длительность] [анимация]
    * toggleParallaxVisibility [индекс] [видим?]
    *
    * ◊ Примеры:
    * 1. Добавить слой облаков над игроком:
    * ◆Команда плагина:AdvancedParallaxLayers, addParallaxLayer, Clouds.png, 0.5, 0, 10, 180
    *
    * 2. Плавное исчезновение слоя:
    * ◆Команда плагина:AdvancedParallaxLayers, animateParallax, 0, opacity, 0, 120, easeOut
    *
    * ◊ Настройки карты (в заметках):
    * <parallaxLayers>
    * Clouds.png, 0.5, 0, 10, 180, 0,0,0,0
    * Fog.png, 0.2, 0.1, 5, 150, 100,100,100,0
    * </parallaxLayers>
    *
    * ◊ Глубина (z-индекс):
    * 0 - Под событиями 5 - Над событиями 10 - Над игроком
    * ================================================== ==========================
    * @param DefaultScrollSpeed
    * @text Скорость прокрутки по умолчанию
    * @desc Стандартная скорость прокрутки (1.0 = обычная скорость параллакса карты)
    * @type number
    * @decimals 2
    * @default 1.00
    *
    * @param AbovePlayerZ
    * @text Z-индекс слоёв над игроком
    * @desc Значение глубины для слоёв, отображаемых над персонажем
    * @type number
    * @default 10
    *
    * @param MaxLayers
    * @text Макс. количество слоёв
    * @desc Максимальное число параллакс-слоёв на карту (влияет на производительность)
    * @type number
    * @default 8
    */

    (() => {
    'use strict';

    // Plugin parameters
    const parameters = PluginManager.parameters('AdvancedParallaxLayers') ;
    const defaultScrollSpeed = parseFloat(parameters['DefaultScrollSpeed'] || 1.0);
    const abovePlayerZ = parseInt(parameters['AbovePlayerZ'] || 10);
    const maxLayers = parseInt(parameters['MaxLayers'] || 8);

    // Runtime data structure
    const _Game_Map_parallaxLayers = new Map();

    // Override map setup to handle our layers
    const _Game_Map_setup = Game_Map.prototype.setup;
    Game_Map.prototype.setup = function(mapId) {
    _Game_Map_setup.call(this, mapId);
    this.setupParallaxLayers();
    };

    Game_Map.prototype.setupParallaxLayers = function() {
    _Game_Map_parallaxLayers.set(this._mapId, []);
    this.loadNotetagLayers();
    };

    Game_Map.prototype.loadNotetagLayers = function() {
    const note = $dataMap.note;
    if (note.includes('<parallaxLayers>')) {
    const layers = note.split('<parallaxLayers>')[1].split('</parallaxLayers>')[0].trim();
    layers.split('\n').forEach(line => {
    const [filename, xSpeed, ySpeed, z, opacity, tint] = line.split(',').map(x => x.trim());
    this.addParallaxLayer(filename, parseFloat(xSpeed), parseFloat(ySpeed), parseInt(z), parseInt(opacity), tint);
    });
    }
    };

    // Core layer management
    Game_Map.prototype.addParallaxLayer = function(filename, xSpeed = defaultScrollSpeed, ySpeed = 0, z = 0, opacity = 255, tint = '0,0,0,0') {
    const layers = _Game_Map_parallaxLayers.get(this._mapId) || [];
    if (layers.length >= maxLayers) return false;

    const layer = {
    filename,
    xSpeed,
    ySpeed,
    z,
    opacity,
    tint: tint.split(',').map(Number),
    x: 0,
    y: 0,
    visible: true,
    animations: []
    };
    layers.push(layer);
    _Game_Map_parallaxLayers.set(this._mapId, layers);
    return true;
    };

    // Rendering integration
    const _Spriteset_Map_createLowerLayer = Spriteset_Map.prototype.createLowerLayer;
    Spriteset_Map.prototype.createLowerLayer = function() {
    _Spriteset_Map_createLowerLayer.call(this);
    this.createParallaxLayers();
    };

    Spriteset_Map.prototype.createParallaxLayers = function() {
    this._parallaxLayers = [];
    const layers = _Game_Map_parallaxLayers.get($gameMap._mapId) || [];
    layers.forEach((layer, index) => {
    const sprite = new TilingSprite();
    sprite.bitmap = ImageManager.loadParallax(layer.filename);
    sprite.move(0, 0, Graphics.width, Graphics.height);
    sprite.z = layer.z;
    sprite.opacity = layer.opacity;
    this._parallaxLayers[index] = sprite;
    this._baseSprite.addChild(sprite);
    });
    };

    // Animation system
    const _Spriteset_Map_update = Spriteset_Map.prototype.update;
    Spriteset_Map.prototype.update = function() {
    _Spriteset_Map_update.call(this);
    this.updateParallaxLayers();
    };

    Spriteset_Map.prototype.updateParallaxLayers = function() {
    const layers = _Game_Map_parallaxLayers.get($gameMap._mapId) || [];
    layers.forEach((layer, index) => {
    const sprite = this._parallaxLayers[index];
    if (!sprite) return;

    // Update position
    layer.x += layer.xSpeed;
    layer.y += layer.ySpeed;
    sprite.origin.x = layer.x % Graphics.width;
    sprite.origin.y = layer.y % Graphics.height;

    // Apply properties
    sprite.z = layer.z;
    sprite.opacity = layer.visible ? layer.opacity : 0;
    sprite.tint = 0xFFFFFF; // Белый цвет (отключает тонирование)

    // Process animations
    this.processLayerAnimations(layer, sprite);
    });
    };

    // Plugin command integration
    PluginManager.registerCommand('AdvancedParallaxLay ers', 'addParallaxLayer', args => {
    $gameMap.addParallaxLayer(
    args.filename,
    parseFloat(args.xSpeed),
    parseFloat(args.ySpeed),
    parseInt(args.z),
    parseInt(args.opacity),
    args.tint
    );
    });

    PluginManager.registerCommand('AdvancedParallaxLay ers', 'animateParallax', args => {
    const layer = this.getLayer(parseInt(args.index));
    if (layer) {
    layer.animations.push({
    property: args.property,
    targetValue: parseFloat(args.value),
    duration: parseInt(args.duration),
    easing: args.easing || 'linear'
    });
    }
    });

    // Helper methods
    Game_Map.prototype.getLayer = function(index) {
    const layers = _Game_Map_parallaxLayers.get(this._mapId) || [];
    return layers[index];
    };

    Spriteset_Map.prototype.processLayerAnimations = function(layer, sprite) {
    layer.animations.forEach((anim, i) => {
    // Animation logic here
    // (Would include interpolation for smooth transitions)
    if (anim.completed) {
    layer.animations.splice(i, 1);
    }
    });
    };

    // Additional utility functions would go here...
    })();


    2 - Увеличение/уменьшение размера спрайта события и персонажа через команды в событиях, графических глюков не было замечено.

    Спойлер Скировать-Вставит:
    /*:
    * @target MZ
    * @plugindesc [v2.2] Масштабирование спрайтов событий, игрока и фолловеров с поддержкой увеличения и уменьшения масштаба. Обновление каждый кадр для устойчивости масштаба.
    * @author Dekita
    *
    * @command ScaleEvent
    * @text Масштабировать Событие/Игрока
    * @desc Меняет масштаб указанного спрайта события или игрока.
    *
    * @arg eventId
    * @type number
    * @text ID События
    * @desc 0 = игрок, -1 = первый фолловер, -2 = второй фолловер и т.д., положительные числа = события на карте.
    * @default 0
    *
    * @arg scaleX
    * @type number
    * @decimals 2
    * @min 0.1
    * @text Масштаб X
    * @desc Масштаб по горизонтали. (Можно уменьшать, например, 0.5)
    * @default 1.0
    *
    * @arg scaleY
    * @type number
    * @decimals 2
    * @min 0.1
    * @text Масштаб Y
    * @desc Масштаб по вертикали. (Можно уменьшать, например, 0.5)
    * @default 1.0
    *
    * @help
    * ──────────────── ──────────────── ─────
    * ???? Использование ноутегов:
    * В примечаниях события:
    * <Scale: 1.5, 1.5> — увеличит
    * <Scale: 0.5, 0.5> — уменьшит
    *
    * ???? Использование команды:
    * ScaleEvent (eventId, scaleX, scaleY)
    *
    * eventId:
    * 0 — игрок
    * -1 — первый фолловер
    * -2 — второй фолловер
    * 1,2,3... — события
    * ──────────────── ──────────────── ─────
    */

    (() => {
    const scaleMap = new WeakMap();

    const _Sprite_Character_update = Sprite_Character.prototype.update;
    Sprite_Character.prototype.update = function() {
    _Sprite_Character_update.call(this);

    if (scaleMap.has(this._character)) {
    const scale = scaleMap.get(this._character);
    this.scale.x = scale.x;
    this.scale.y = scale.y;
    }
    };

    const _Sprite_Character_setCharacterBitmap = Sprite_Character.prototype.setCharacterBitmap;
    Sprite_Character.prototype.setCharacterBitmap = function() {
    _Sprite_Character_setCharacterBitmap.call(this);

    if (this._character instanceof Game_Event) {
    const event = $dataMap.events[this._character.eventId()];
    if (event && event.note) {
    const match = event.note.match(/<Scale:\s*(\d+(\.\d+)?),\s*(\d+(\.\d+)?)>/i);
    if (match) {
    const scaleX = Math.max(0.1, parseFloat(match[1])); // Минимум 0.1 чтобы избежать невидимости
    const scaleY = Math.max(0.1, parseFloat(match[3]));
    scaleMap.set(this._character, { x: scaleX, y: scaleY });
    }
    }
    }
    };

    PluginManager.registerCommand("DKR_SpriteScaler", "ScaleEvent", args => {
    const eventId = Number(args.eventId);
    const scaleX = Math.max(0.1, parseFloat(args.scaleX) || 1.0);
    const scaleY = Math.max(0.1, parseFloat(args.scaleY) || 1.0);
    let character = null;

    if (eventId === 0) {
    character = $gamePlayer;
    } else if (eventId < 0) {
    const index = Math.abs(eventId) - 1;
    character = $gamePlayer.followers().follower(index);
    } else {
    character = $gameMap.event(eventId);
    }

    if (!character) return;
    scaleMap.set(character, { x: scaleX, y: scaleY });
    });
    })();


    3 - Дальше идут уже под боёвку. Добавляет 6 наименнований, что могут являться например характеристиками или хоть слотами под гранаты. У каждой такой характеристики имеется состояние, что отображается в виде иконки, что в свою очередь можно легко поменять, иконки теже, что используются в БД. Состояний всего 3 (изначально была идея: Ослабленое, стабильно, перегруженное. Потом думал использовать для игры про будущее, где бы они играли роль кнопок вкл/выкл/сломана) и все они одинаковые для всех 6 характеристик. Какое состояние будет у характеристики определяется в начале боя SRPG рандомно.

    Спойлер Скировать-Вставит:
    /*:
    * @target MZ
    * @plugindesc [RUS] Дополнительные параметры для SRPG_Core — характеристики актёров с состояниями.
    * @author DK
    * @help
    *
    * Этот плагин добавляет 6 дополнительных характеристик для актёров в бою SRPG:
    * - Сила
    * - Ловкость
    * - Восприятие
    * - Стойкость
    * - Интеллект
    * - Харизма
    *
    * Каждая характеристика может находиться в одном из состояний:
    * - Ослабленное (иконка 12)
    * - Стабильное (иконка 14)
    * - Перегруженное (иконка 13)
    *
    * Настройки можно редактировать через меню плагинов.
    *
    * ДАННЫЕ НЕ СОХРАНЯЮТСЯ после боя. Характеристики генерируются случайно каждый раз.
    *
    * ---
    * Настройки:
    *
    * @param Characteristics
    * @text Характеристики
    * @type struct<Characteristics>[]
    * @default ["{"Name":"Сила"}","{"Name":"Ловкость"} ","{"Name":"Восприятие"}","{"Name":"Ст ойкость"}","{"Name":"Интеллект"}", "{"Name":"Харизма"}"]
    *
    * @param States
    * @text Состояния
    * @type struct<State>[]
    * @default ["{"Name":"Ослабленное","IconIndex":"12" }","{"Name":"Стабильное","IconIndex":"14 "}","{"Name":"Перегруженное","IconInd ex":"13"}"]
    *
    * @param StartX
    * @text Начальная позиция X
    * @desc Позиция по оси X, с которой начинается отображение характеристик.
    * @type number
    * @default 360
    */

    /*~struct~Characteristics:
    * @param Name
    * @text Название характеристики
    * @type text
    * @default Новая характеристика
    */

    /*~struct~State:
    * @param Name
    * @text Название состояния
    * @type text
    * @default Новое состояние
    *
    * @param IconIndex
    * @text Номер иконки
    * @type number
    * @default 0
    */

    (() => {
    const pluginName = "RUS_SRPG_ExtendedStats";
    const parameters = PluginManager.parameters(pluginName);

    const characteristics = JSON.parse(parameters["Characteristics"] || "[]").map(e => JSON.parse(e));
    const states = JSON.parse(parameters["States"] || "[]").map(e => JSON.parse(e));

    // Глобальное хранилище характеристик
    window.SRPG_ExtendedStats = {
    _data: {},

    randomizeCharacteristics(actorId) {
    if (!actorId) return;
    if (!this._data) this._data = {};

    const actorData = [];
    const minStable = 1; // минимум характеристик в стабильном состоянии
    const maxStable = 4; // максимум характеристик в стабильном состоянии

    const stableCount = Math.max(minStable, Math.floor(Math.random() * (maxStable - minStable + 1)) + minStable);

    // Сначала заполняем массив статусами
    const statuses = Array(characteristics.length).fill(1); // 1 = Стабильное
    let left = characteristics.length - stableCount;

    for (let i = 0; i < statuses.length; i++) {
    if (left > 0) {
    const randomState = Math.random() < 0.5 ? 0 : 2; // 0 = Ослабленное, 2 = Перегруженное
    statuses[i] = randomState;
    left--;
    }
    }

    // Перемешиваем состояния
    for (let i = statuses.length - 1; i > 0; i--) {
    const j = Math.floor(Math.random() * (i + 1));
    [statuses[i], statuses[j]] = [statuses[j], statuses[i]];
    }

    // Сохраняем
    this._data[actorId] = statuses;

    console.log(`✅ Характеристики для актёра ID ${actorId} сгенерированы:`, statuses);
    },

    getCharacteristicState(actorId, index) {
    if (!this._data || !this._data[actorId]) return null;
    return this._data[actorId][index];
    }
    };
    })();


    4 - Технический плагин, что как раз отображает всю информацию выше, возможно его можно вставить прямо в верхний плагин.

    Спойлер Скировать-Вставит:
    (function() {
    const pluginName = "RUS_SRPG_ExtendedStats";

    const _Window_SrpgActorCommandStatus_drawActorItemStatus = Window_SrpgActorCommandStatus.prototype.drawActorI temStatus;
    Window_SrpgActorCommandStatus.prototype.drawActorI temStatus = function() {
    _Window_SrpgActorCommandStatus_drawActorItemStatus .call(this);

    if (!this._battler || !this._battler.isActor?.()) return;

    const actorId = this._battler.actorId();

    if (!window.SRPG_ExtendedStats) {
    console.warn("⚠️ SRPG_ExtendedStats не найден!");
    return;
    }

    if (!SRPG_ExtendedStats._data) {
    SRPG_ExtendedStats._data = {};
    }

    // Если у актора ещё нет характеристик - генерируем их!
    if (!SRPG_ExtendedStats._data[actorId]) {
    console.log(`⚡ Генерация характеристик для актора ID ${actorId}`);
    SRPG_ExtendedStats.randomizeCharacteristics(actorI d);
    }

    const charData = SRPG_ExtendedStats._data[actorId];
    if (!charData) {
    console.warn(`⚠️ Нет характеристик для актора ID ${actorId}`);
    return;
    }

    const parameters = PluginManager.parameters(pluginName);
    const characteristics = JSON.parse(parameters["Characteristics"] || "[]").map(e => JSON.parse(e));
    const states = JSON.parse(parameters["States"] || "[]").map(e => JSON.parse(e));
    const startX = Number(parameters["StartX"] || "360"); // Настраиваемая позиция по X

    const lineHeight = this.lineHeight();
    const columnWidth = 170;
    const rowHeight = lineHeight;

    for (let i = 0; i < characteristics.length; i++) {
    const chara = characteristics[i];
    const stateIndex = SRPG_ExtendedStats.getCharacteristicState(actorId, i);
    if (stateIndex == null) continue;
    const state = states[stateIndex];

    const iconId = Number(state.IconIndex) || 0;
    const name = chara.Name || `Характеристика ${i + 1}`;

    const column = i % 2; // 0 = левая колонка, 1 = правая колонка
    const row = Math.floor(i / 2);

    const x = startX + column * columnWidth;
    const y = row * rowHeight;

    this.contents.fontSize = 18;
    this.contents.textColor = ColorManager.normalColor();
    this.contents.drawText(name, x, y, 120, lineHeight, "left");

    if (iconId > 0) {
    this.drawIcon(iconId, x + 130, y + 2);
    }
    }
    };
    })();


    5 - Плагин, что позволяет менять состояния различнейшим образом с помощью навыков.

    Спойлер Скировать-Вставит:
    /*:
    * @target MZ
    * @plugindesc [RUS] Управление влиянием навыков на состояния характеристик SRPG.
    * @author DK
    *
    * @help
    * ================================================== ==========================
    * RUS_SRPG_ExtendedStats_Skills - Руководство
    * ================================================== ==========================
    *
    * Этот плагин позволяет навыкам влиять на состояния характеристик SRPG.
    *
    * ⚠️ Требования:
    * - Плагин RUS_SRPG_ExtendedStats должен быть включен и находиться ВЫШЕ
    *
    * ============================== Основные возможности ========================
    *
    * 1. Изменение нескольких характеристик одновременно
    * 2. Временные изменения (на N ходов)
    * 3. Настройка шанса срабатывания эффекта
    * 4. Гибкое управление переполнением состояний
    *
    * ============================== Настройка навыков ===========================
    *
    * Для настройки эффектов:
    * 1. Откройте параметры плагина
    * 2. Добавьте новый элемент в "SkillsSettings"
    * 3. Заполните параметры:
    *
    * - SkillId: ID навыка из базы данных
    * - AffectedCharacteristics: список изменяемых характеристик
    * * CharacteristicIndex: номер характеристики (0-5)
    * * Mode: режим изменения (set/shift/wrap)
    * * Value: значение изменения
    * * Duration: длительность в ходах (0=навсегда)
    * * Chance: шанс срабатывания (1-100)
    * * OverflowBehavior: поведение при выходе за пределы
    *
    * ============================== Режимы изменения ============================
    *
    * 1. set - установить точное значение (Value)
    * 2. shift - изменить текущее значение на Value
    * 3. wrap - циклическое изменение (при выходе за пределы)
    *
    * ========================= Поведение при переполнении =======================
    *
    * 1. block - блокировать изменение
    * 2. wrap - циклическое изменение (3→0, -1→2)
    * 3. reverse - обратное изменение (3→1, -1→1)
    *
    * ============================== Примеры настроек ============================
    *
    * 1. Временное усиление (3 хода):
    * Mode: shift, Value: 1, Duration: 3, Overflow: block
    *
    * 2. Случайное ослабление (50% шанс):
    * Mode: shift, Value: -1, Chance: 50
    *
    * 3. Циклическое изменение:
    * Mode: wrap, Value: 1, Overflow: wrap
    *
    * ============================== Техническая информация ======================
    *
    * Состояния характеристик:
    * 0 - Ослабленное
    * 1 - Стабильное
    * 2 - Перегруженное
    *
    * Все изменения логируются в консоль F8
    *
    * ================================================== ==========================
    * Конец руководства
    * ================================================== ==========================
    * ---
    *
    * @param SkillsSettings
    * @text Настройки Навыков
    * @type struct<SkillSetting>[]
    * @default []
    *
    */

    /*~struct~SkillSetting:
    * @param SkillId
    * @text ID навыка
    * @type number
    * @desc ID навыка из базы данных
    *
    * @param AffectedCharacteristics
    * @text Изменяемые характеристики
    * @type struct<CharacteristicEffect>[]
    * @default []
    */

    /*~struct~CharacteristicEffect:
    * @param CharacteristicIndex
    * @text Индекс характеристики
    * @type number
    * @desc Номер характеристики (от 0)
    *
    * @param Mode
    * @text Режим изменения
    * @type select
    * @option set
    * @option shift
    * @option wrap
    * @default shift
    *
    * @param Value
    * @text Значение изменения
    * @type number
    * @desc Например: 1, -1 или 0
    *
    * @param Duration
    * @text Длительность ходов
    * @type number
    * @default 0
    * @desc 0 = навсегда
    *
    * @param Chance
    * @text Шанс применения (%)
    * @type number
    * @default 100
    *
    * @param OverflowBehavior
    * @text При выходе за пределы
    * @type select
    * @option block
    * @option wrap
    * @option reverse
    * @default reverse
    */


    (() => {
    const pluginName = "RUS_SRPG_ExtendedStats_Skills"; // ⚡ Название файла без .js

    const _Game_Action_apply = Game_Action.prototype.apply;
    Game_Action.prototype.apply = function(target) {
    _Game_Action_apply.call(this, target);

    if (!this.item() || this.item().damage.type === 0) return; // Пропустить если навык ничего не делает

    const settingsArray = JSON.parse(PluginManager.parameters(pluginName)["SkillsSettings"] || "[]");
    if (!settingsArray.length) return;

    const skillSettingRaw = settingsArray.find(setting => {
    return JSON.parse(setting).SkillId == this.item().id;
    });
    if (!skillSettingRaw) return;

    const skillSetting = JSON.parse(skillSettingRaw);
    const affects = JSON.parse(skillSetting.AffectedCharacteristics || "[]").map(e => JSON.parse(e));

    if (!affects.length) return;

    const actor = this.subject().isActor() ? this.subject() : null;
    if (!actor) return;

    const actorId = actor.actorId();
    const data = SRPG_ExtendedStats._data[actorId];
    if (!data) return;

    affects.forEach(effect => {
    const index = Number(effect.CharacteristicIndex);
    const mode = effect.Mode || "shift";
    const value = Number(effect.Value || 0);
    const duration = Number(effect.Duration || 0);
    const chance = Number(effect.Chance || 100);
    const overflow = effect.OverflowBehavior || "reverse";

    if (Math.random() * 100 > chance) {
    console.log(`???? Характеристика ${index}: шанс ${chance}% не сработал.`);
    return;
    }

    const oldState = data[index];
    let newState = oldState;

    if (mode === "set") {
    newState = value;
    } else if (mode === "shift" || mode === "wrap") {
    newState = oldState + value;

    const maxState = 2; // 0: ослабленное, 1: стабильное, 2: перегруженное
    const minState = 0;

    if (newState > maxState || newState < minState) {
    if (overflow === "block") {
    newState = oldState; // Блокировать изменение
    } else if (overflow === "wrap") {
    if (newState > maxState) newState = minState;
    else if (newState < minState) newState = maxState;
    } else if (overflow === "reverse") {
    if (newState > maxState) {
    newState = oldState - value;
    } else if (newState < minState) {
    newState = oldState - value;
    }
    }
    }
    }

    data[index] = newState;

    console.log(`???? [${index}] ${SRPG_ExtendedStats.characteristicName(index)}: ${SRPG_ExtendedStats.stateName(oldState)} ➔ ${SRPG_ExtendedStats.stateName(newState)}`);
    });

    console.log(`✨ Навык ID ${this.item().id} применил изменения на актёре ID ${actorId}`);
    };

    // ???? Дополнительные утилиты для красивых логов
    SRPG_ExtendedStats.characteristicName = function(index) {
    const params = PluginManager.parameters("RUS_SRPG_ExtendedStats") ;
    const chara = JSON.parse(params["Characteristics"] || "[]").map(e => JSON.parse(e))[index];
    return chara ? chara.Name : `Характеристика ${index}`;
    };

    SRPG_ExtendedStats.stateName = function(stateIndex) {
    const params = PluginManager.parameters("RUS_SRPG_ExtendedStats") ;
    const states = JSON.parse(params["States"] || "[]").map(e => JSON.parse(e));
    const state = states[stateIndex];
    return state ? state.Name : `Состояние ${stateIndex}`;
    };

    })();

    // ================================================== ===================
    // Вторая часть: временные изменения характеристик
    // ================================================== ===================

    // Создаём список активных временных эффектов
    SRPG_ExtendedStats._timedEffects = [];

    // Хук в обновление игры (очистка временных эффектов)
    const _SRPG_SceneMap_update = Scene_Map.prototype.update;
    Scene_Map.prototype.update = function() {
    _SRPG_SceneMap_update.call(this);
    SRPG_ExtendedStats.updateTimedEffects();
    };

    // Функция обновления временных эффектов каждый ход
    SRPG_ExtendedStats.updateTimedEffects = function() {
    if (!$gameSystem.isSRPGMode()) return; // Только в SRPG режиме

    for (const effect of this._timedEffects) {
    effect.duration--;

    if (effect.duration <= 0) {
    // Возвращаем старое состояние
    const data = this._data[effect.actorId];
    if (data) {
    data[effect.characteristicIndex] = effect.originalState;

    console.log(`⏳ Временный эффект закончился! Характеристика [${effect.characteristicIndex}] у актёра ID ${effect.actorId} восстановлена до состояния ${this.stateName(effect.originalState)}.`);
    }
    }
    }

    // Очищаем завершённые эффекты
    this._timedEffects = this._timedEffects.filter(effect => effect.duration > 0);
    };

    // Модификация применения навыка: сохраняем оригинальные состояния если Duration > 0
    const _Game_Action_apply_Saved = Game_Action.prototype.apply;
    Game_Action.prototype.apply = function(target) {
    const preEffects = SRPG_ExtendedStats._timedEffects.slice(); // Сохраняем предыдущее состояние временных эффектов

    _Game_Action_apply_Saved.call(this, target);

    // После применения - ищем, что изменилось и создаём временные эффекты
    const settingsArray = JSON.parse(PluginManager.parameters("ТВОЁ_ИМ Я_ПЛАГИНА")["SkillsSettings"] || "[]");
    if (!settingsArray.length) return;

    const skillSettingRaw = settingsArray.find(setting => {
    return JSON.parse(setting).SkillId == this.item().id;
    });
    if (!skillSettingRaw) return;

    const skillSetting = JSON.parse(skillSettingRaw);
    const affects = JSON.parse(skillSetting.AffectedCharacteristics || "[]").map(e => JSON.parse(e));
    if (!affects.length) return;

    const actor = this.subject().isActor() ? this.subject() : null;
    if (!actor) return;

    const actorId = actor.actorId();
    const data = SRPG_ExtendedStats._data[actorId];
    if (!data) return;

    affects.forEach(effect => {
    const index = Number(effect.CharacteristicIndex);
    const duration = Number(effect.Duration || 0);

    if (duration > 0) {
    const originalState = preEffects.find(eff => eff.actorId === actorId && eff.characteristicIndex === index)
    ? preEffects.find(eff => eff.actorId === actorId && eff.characteristicIndex === index).originalState
    : data[index];

    SRPG_ExtendedStats._timedEffects.push({
    actorId: actorId,
    characteristicIndex: index,
    originalState: originalState,
    duration: duration
    });

    console.log(`⏳ Временный эффект: характеристика [${index}] у актёра ID ${actorId} изменена на ${duration} ход(ов).`);
    }
    });
    };


    6 - Плагин, что даёт менять шрифт текста в диалогах во время боя SRPG.

    Спойлер Скировать-Вставит:
    /*:
    * @target MZ
    * @plugindesc [RUS] Изменение шрифтов SRPG по вкладкам во время боя и восстановление после боя.
    * @author DK
    *
    * @help
    *
    * Этот плагин позволяет:
    * - Изменять шрифт отдельно для разных частей интерфейса SRPG боя.
    * - Автоматически восстанавливать шрифт после боя или выхода в главное меню.
    *
    * ---
    *
    * @param FontSettings
    * @text Настройки шрифтов для SRPG
    * @type struct<FontSetting>[]
    * @default []
    *
    */

    /*~struct~FontSetting:
    * @param Area
    * @text Зона интерфейса
    * @type select
    * @option Имя
    * @option HP/MP/TP
    * @option Атака/Защита и т.д. (параметры врагов)
    * @option Бой с противником (лог боя)
    * @option Наши Характеристики (доп. плагин)
    * @option Меню выбора действий (атаковать, предметы и т.д.)
    * @option Навыки
    * @option Системное меню (Победа/Поражение/Состояния)
    *
    * @param FontFace
    * @text Название шрифта
    * @type string
    * @default GameFont
    *
    * @param FontSize
    * @text Размер шрифта
    * @type number
    * @default 20
    */
    (() => {
    const pluginName = "SRPG_FontChanger";

    const parameters = PluginManager.parameters(pluginName);
    const fontSettingsRaw = JSON.parse(parameters["FontSettings"] || "[]");
    const fontSettings = {};

    // Обрабатываем параметры в удобный формат
    for (const entry of fontSettingsRaw) {
    const setting = JSON.parse(entry);
    fontSettings[setting.Area] = {
    fontFace: setting.FontFace,
    fontSize: Number(setting.FontSize)
    };
    }

    // Храним оригинальные значения шрифта
    const OriginalFont = {
    face: null,
    size: null
    };

    // Функция: применить шрифт по зоне
    function applyFont(area) {
    if (!fontSettings[area]) return;

    const setting = fontSettings[area];
    if (setting.fontFace) {
    $gameSystem.setSrpgFontFace(setting.fontFace);
    }
    if (setting.fontSize) {
    $gameSystem.setSrpgFontSize(setting.fontSize);
    }
    }

    // Функция: восстановить оригинальный шрифт
    function restoreFont() {
    if (OriginalFont.face) {
    $gameSystem.setSrpgFontFace(OriginalFont.face);
    }
    if (OriginalFont.size) {
    $gameSystem.setSrpgFontSize(OriginalFont.size);
    }
    }

    // Сохраняем оригинальный шрифт в начале игры
    const _Scene_Boot_start = Scene_Boot.prototype.start;
    Scene_Boot.prototype.start = function() {
    _Scene_Boot_start.call(this);
    OriginalFont.face = $gameSystem.srpgFontFace();
    OriginalFont.size = $gameSystem.srpgFontSize();
    };

    // Переопределяем функции для получения шрифта
    const _Window_Base_resetFontSettings = Window_Base.prototype.resetFontSettings;
    Window_Base.prototype.resetFontSettings = function() {
    _Window_Base_resetFontSettings.call(this);

    if ($gameSystem.isSRPGMode?.() && $gameSystem.srpgFontFace()) {
    this.contents.fontFace = $gameSystem.srpgFontFace();
    this.contents.fontSize = $gameSystem.srpgFontSize();
    }
    };

    // Расширяем $gameSystem для хранения шрифта SRPG
    const _Game_System_initialize = Game_System.prototype.initialize;
    Game_System.prototype.initialize = function() {
    _Game_System_initialize.call(this);
    this._srpgFontFace = null;
    this._srpgFontSize = null;
    };

    Game_System.prototype.setSrpgFontFace = function(font) {
    this._srpgFontFace = font;
    };

    Game_System.prototype.setSrpgFontSize = function(size) {
    this._srpgFontSize = size;
    };

    Game_System.prototype.srpgFontFace = function() {
    return this._srpgFontFace;
    };

    Game_System.prototype.srpgFontSize = function() {
    return this._srpgFontSize;
    };

    // Перехват начала SRPG боя
    const _Game_System_startSRPG = Game_System.prototype.startSRPG;
    Game_System.prototype.startSRPG = function() {
    _Game_System_startSRPG.call(this);
    console.log("⚡ Бой SRPG начался — шрифт SRPG активирован!");
    applyFont("Бой с противником (лог боя)");
    };

    // Перехват окончания SRPG боя
    const _Game_System_endSRPG = Game_System.prototype.endSRPG;
    Game_System.prototype.endSRPG = function() {
    _Game_System_endSRPG.call(this);
    console.log("✅ Бой SRPG завершён — шрифт восстановлен!");
    restoreFont();
    };

    })();


    7 - Плагин, что рандомизирует сообщения в битве и добавляет возможность показывать рандомные сообщения, что зависят от выполнения определённых условий. Если не вру, то может работать и в обычном бою RPG Maker. Обучения я случайно удалил, но главная суть, что нужно вставить следующее сообщение в примечание навыка, игра будет определять сначала самое верхнее сообщение, если его условие будет выполнено (кроме normal, оно будет использоваться, если остальные требования не будут выполнены). За что отвечает каждый параметр вроде как можно косвенно определить по сообщениям.

    <skillMessages>
    normal: ["Обычная атака!", "Получай!"]
    highDamage>=200: ["Мощный удар!", "Разрушительный крит!"]
    highDamage<50: ["Слабенько!", "Это всё?"]
    lowHp<=0.3: ["Ты почти труп!", "Последний вдох!"]
    lowMp<=0.2: ["У тебя почти нет маны!", "На исходе!"]
    variable[5]>=10: ["Время пришло!", "Настал момент!"]
    level>=5: ["Я уже не новичок!", "Я вырос!"]
    state[10]: ["Ты отравлен!", "Я воспользуюсь твоей слабостью!"]
    </skillMessages>

    Спойлер Скировать-Вставит:
    /*:
    * @plugindesc v1.2.0 [MZ] Показывает случайные сообщения при использовании навыков или предметов на основе условий. Совместим с SRPG_Core.
    * @author Custom for user
    * @target MZ
    * @url https://dk-plugins.ru
    *
    * @help
    * Этот плагин позволяет отображать случайные сообщения при использовании навыков или предметов,
    * в зависимости от заданных условий. Поддерживает RPG Maker MZ и совместим с SRPG_Core.
    *
    * ???? Использование:
    * В заметки навыка или предмета добавьте блок:
    *
    * <skillMessages>
    * normal: ["Обычная атака!", "Получай!"]
    * highDamage>=200: ["Мощный удар!", "Разрушительный крит!"]
    * highDamage<50: ["Слабенько!", "Это всё?"]
    * lowHp<=0.3: ["Ты почти труп!", "Последний вдох!"]
    * lowMp<=0.2: ["У тебя почти нет маны!", "На исходе!"]
    * variable[5]>=10: ["Время пришло!", "Настал момент!"]
    * level>=5: ["Я уже не новичок!", "Я вырос!"]
    * state[10]: ["Ты отравлен!", "Я воспользуюсь твоей слабостью!"]
    * </skillMessages>
    *
    * ???? Поддерживаемые условия:
    * - highDamage>=X — если урон больше или равен X
    * - highDamage<X — если урон меньше X
    * - lowHp<=Y — если HP цели меньше или равно Y (доля, от 0 до 1)
    * - lowMp<=Y — если MP цели меньше или равно Y (доля, от 0 до 1)
    * - variable[ID]>=N — значение переменной >= N
    * - level>=X — уровень цели
    * - state[ID] — если цель под действием состояния ID
    *
    * ???? Приоритет условий:
    * Проверяются сверху вниз. Срабатывает первое подходящее условие.
    * Если ни одно не подошло — используется блок "normal", если он задан.
    */

    (() => {
    const _Game_Action_apply = Game_Action.prototype.apply;
    Game_Action.prototype.apply = function(target) {
    _Game_Action_apply.call(this, target);
    if (!this.item() || !$gameParty.inBattle()) return;

    const skill = this.item();
    const notes = skill.note;
    const match = notes.match(/<skillMessages>[\s\S]*?<\/skillMessages>/);
    if (!match) return;

    const block = match[0];
    const lines = block.split(/\r?\n/).slice(1, -1);

    const messages = { normal: [] };
    const conditions = [];

    for (let line of lines) {
    line = line.trim();
    if (line.startsWith("normal:")) {
    eval("messages.normal.push(..." + line.slice(7).trim() + ")");
    } else if (line.startsWith("highDamage>=")) {
    const val = Number(line.match(/highDamage>=(\d+)/)[1]);
    const msgs = eval(line.split(":")[1]);
    conditions.push({ type: "highDamageGTE", val, msgs });
    } else if (line.startsWith("highDamage<")) {
    const val = Number(line.match(/highDamage<(\d+)/)[1]);
    const msgs = eval(line.split(":")[1]);
    conditions.push({ type: "highDamageLT", val, msgs });
    } else if (line.startsWith("lowHp<=")) {
    const val = parseFloat(line.match(/lowHp<=([\d.]+)/)[1]);
    const msgs = eval(line.split(":")[1]);
    conditions.push({ type: "lowHpLTE", val, msgs });
    } else if (line.startsWith("lowMp<=")) {
    const val = parseFloat(line.match(/lowMp<=([\d.]+)/)[1]);
    const msgs = eval(line.split(":")[1]);
    conditions.push({ type: "lowMpLTE", val, msgs });
    } else if (line.match(/^variable\[\d+\]/)) {
    const m = line.match(/^variable\[(\d+)\]>=?(\d+)/);
    if (m) {
    const id = Number(m[1]);
    const val = Number(m[2]);
    const msgs = eval(line.split(":")[1]);
    conditions.push({ type: "variableGTE", id, val, msgs });
    }
    } else if (line.startsWith("level>=")) {
    const val = Number(line.match(/level>=(\d+)/)[1]);
    const msgs = eval(line.split(":")[1]);
    conditions.push({ type: "levelGTE", val, msgs });
    } else if (line.startsWith("state[")) {
    const id = Number(line.match(/state\[(\d+)\]/)[1]);
    const msgs = eval(line.split(":")[1]);
    conditions.push({ type: "state", id, msgs });
    }
    }

    const damage = target._result.hpDamage || 0;
    const hpRate = target.hpRate();
    const mpRate = target.mpRate();
    let message = null;

    for (const cond of conditions) {
    if (cond.type === "highDamageGTE" && damage >= cond.val) {
    message = cond.msgs[Math.floor(Math.random() * cond.msgs.length)];
    break;
    } else if (cond.type === "highDamageLT" && damage < cond.val) {
    message = cond.msgs[Math.floor(Math.random() * cond.msgs.length)];
    break;
    } else if (cond.type === "lowHpLTE" && hpRate <= cond.val) {
    message = cond.msgs[Math.floor(Math.random() * cond.msgs.length)];
    break;
    } else if (cond.type === "lowMpLTE" && mpRate <= cond.val) {
    message = cond.msgs[Math.floor(Math.random() * cond.msgs.length)];
    break;
    } else if (cond.type === "variableGTE" && $gameVariables.value(cond.id) >= cond.val) {
    message = cond.msgs[Math.floor(Math.random() * cond.msgs.length)];
    break;
    } else if (cond.type === "levelGTE" && target.level && target.level >= cond.val) {
    message = cond.msgs[Math.floor(Math.random() * cond.msgs.length)];
    break;
    } else if (cond.type === "state" && target.isStateAffected(cond.id)) {
    message = cond.msgs[Math.floor(Math.random() * cond.msgs.length)];
    break;
    }
    }

    if (!message && messages.normal.length) {
    message = messages.normal[Math.floor(Math.random() * messages.normal.length)];
    }

    if (message) {
    if ($gameSystem.pushSrpgLog) {
    $gameSystem.pushSrpgLog(message);
    } else {
    const logWindow = SceneManager._scene?._logWindow;
    if (logWindow?.addText) logWindow.addText(message);
    }
    }
    };
    })();


    8 - Позволяет запускать глобальные события до применения навыка на противнике, но при его выборе. Идея заключалась в том, что можно было бы запускать цепочку выборов, что позволяли на ходу видоизменить навык и уже изменёный навык можно было бы использовать на противнике. Но данную идею я отложил на потом.

    Спойлер Скировать-Вставит:
    /*:
    * @target MZ
    * @plugindesc Расширенный контроль глобальных событий для SRPG-навыков
    * @author Ваше имя
    * @base SRPG_core_MZ
    * @orderAfter SRPG_core_MZ
    *
    * @help
    * = Как использовать =
    * Добавьте в описание навыка любые комбинации тегов:
    *
    * <onSkillSelect:X> - Срабатывает сразу при выборе навыка
    * <onTargetSelect:Y> - Срабатывает при выборе цели (до боя)
    * <onBattleStart:Z> - Срабатывает при начале боя
    * <onBattleEnd:W> - Срабатывает после окончания боя
    *
    * Пример:
    * <onSkillSelect:10> - Событие 10 при выборе навыка
    * <onTargetSelect:11> - Событие 11 при выборе цели
    * <onBattleStart:12> - Событие 12 при начале боя
    * <onBattleEnd:13> - Событие 13 после боя
    */

    (() => {
    'use strict';

    // Хранит текущий выбранный навык
    let _selectedSkill = null;

    // Получаем ID событий из тегов навыка
    const getSkillEventIds = function(skill) {
    if (!skill || !skill.meta) return {};
    return {
    onSelect: skill.meta.onSkillSelect ? parseInt(skill.meta.onSkillSelect) : null,
    onTarget: skill.meta.onTargetSelect ? parseInt(skill.meta.onTargetSelect) : null,
    onStart: skill.meta.onBattleStart ? parseInt(skill.meta.onBattleStart) : null,
    onEnd: skill.meta.onBattleEnd ? parseInt(skill.meta.onBattleEnd) : null
    };
    };

    // 1. Перехват выбора навыка через Game_Action
    const _Game_Action_setSkill = Game_Action.prototype.setSkill;
    Game_Action.prototype.setSkill = function(skillId) {
    _Game_Action_setSkill.call(this, skillId);
    if (this.isSkill()) {
    _selectedSkill = this.item();
    const { onSelect } = getSkillEventIds(_selectedSkill);
    if (onSelect) $gameTemp.reserveCommonEvent(onSelect);
    }
    };

    // 2. Перехват выбора цели
    const _Game_Player_triggerAction = Game_Player.prototype.triggerAction;
    Game_Player.prototype.triggerAction = function() {
    if ($gameSystem.isSRPGMode() && $gameSystem.isSubBattlePhase() === 'actor_target') {
    if (_selectedSkill) {
    const { onTarget } = getSkillEventIds(_selectedSkill);
    if (onTarget) $gameTemp.reserveCommonEvent(onTarget);
    }
    }
    return _Game_Player_triggerAction.call(this);
    };

    // 3. Перехват начала боя
    const _Scene_Map_srpgBattleStart = Scene_Map.prototype.srpgBattleStart;
    Scene_Map.prototype.srpgBattleStart = function(userArray, targetArray) {
    if (_selectedSkill) {
    const { onStart } = getSkillEventIds(_selectedSkill);
    if (onStart) $gameTemp.reserveCommonEvent(onStart);
    }
    _Scene_Map_srpgBattleStart.call(this, userArray, targetArray);
    };

    // 4. Перехват окончания боя
    const _Scene_Map_srpgAfterAction = Scene_Map.prototype.srpgAfterAction;
    Scene_Map.prototype.srpgAfterAction = function() {
    if (_selectedSkill) {
    const { onEnd } = getSkillEventIds(_selectedSkill);
    if (onEnd) $gameTemp.reserveCommonEvent(onEnd);
    _selectedSkill = null;
    }
    _Scene_Map_srpgAfterAction.call(this);
    };

    // Очистка при отмене выбора
    const _Game_Actor_clearActions = Game_Actor.prototype.clearActions;
    Game_Actor.prototype.clearActions = function() {
    _selectedSkill = null;
    _Game_Actor_clearActions.call(this);
    };

    })();
    Последний раз редактировалось BaronDered; 20.04.2025 в 11:06.

Информация о теме

Пользователи, просматривающие эту тему

Эту тему просматривают: 1 (пользователей: 0 , гостей: 1)

Метки этой темы

Социальные закладки

Социальные закладки

Ваши права

  • Вы не можете создавать новые темы
  • Вы не можете отвечать в темах
  • Вы не можете прикреплять вложения
  • Вы не можете редактировать свои сообщения
  •  
[MZ] Плагины сделанные с помощью ИИ